Cleaning Robot
Time Limit: 1000MS | Memory Limit: 65536K | |
Total Submissions: 4395 | Accepted: 1763 |
Description
Here, we want to solve path planning for a mobile robot cleaning a rectangular room floor with furniture.
Consider the room floor paved with square tiles whose size fits the cleaning robot (1 * 1). There are 'clean tiles' and 'dirty tiles', and the robot can change a 'dirty tile' to a 'clean tile' by visiting the tile. Also there may be some obstacles (furniture) whose size fits a tile in the room. If there is an obstacle on a tile, the robot cannot visit it. The robot moves to an adjacent tile with one move. The tile onto which the robot moves must be one of four tiles (i.e., east, west, north or south) adjacent to the tile where the robot is present. The robot may visit a tile twice or more.
Your task is to write a program which computes the minimum number of moves for the robot to change all 'dirty tiles' to 'clean tiles', if ever possible.
Consider the room floor paved with square tiles whose size fits the cleaning robot (1 * 1). There are 'clean tiles' and 'dirty tiles', and the robot can change a 'dirty tile' to a 'clean tile' by visiting the tile. Also there may be some obstacles (furniture) whose size fits a tile in the room. If there is an obstacle on a tile, the robot cannot visit it. The robot moves to an adjacent tile with one move. The tile onto which the robot moves must be one of four tiles (i.e., east, west, north or south) adjacent to the tile where the robot is present. The robot may visit a tile twice or more.
Your task is to write a program which computes the minimum number of moves for the robot to change all 'dirty tiles' to 'clean tiles', if ever possible.
Input
The
input consists of multiple maps, each representing the size and
arrangement of the room. A map is given in the following format.
w h
c11 c12 c13 ... c1w
c21 c22 c23 ... c2w
...
ch1 ch2 ch3 ... chw
The integers w and h are the lengths of the two sides of the floor of the room in terms of widths of floor tiles. w and h are less than or equal to 20. The character cyx represents what is initially on the tile with coordinates (x, y) as follows.
'.' : a clean tile
'*' : a dirty tile
'x' : a piece of furniture (obstacle)
'o' : the robot (initial position)
In the map the number of 'dirty tiles' does not exceed 10. There is only one 'robot'.
The end of the input is indicated by a line containing two zeros.
w h
c11 c12 c13 ... c1w
c21 c22 c23 ... c2w
...
ch1 ch2 ch3 ... chw
The integers w and h are the lengths of the two sides of the floor of the room in terms of widths of floor tiles. w and h are less than or equal to 20. The character cyx represents what is initially on the tile with coordinates (x, y) as follows.
'.' : a clean tile
'*' : a dirty tile
'x' : a piece of furniture (obstacle)
'o' : the robot (initial position)
In the map the number of 'dirty tiles' does not exceed 10. There is only one 'robot'.
The end of the input is indicated by a line containing two zeros.
Output
For
each map, your program should output a line containing the minimum
number of moves. If the map includes 'dirty tiles' which the robot
cannot reach, your program should output -1.
Sample Input
7 5 ....... .o...*. ....... .*...*. ....... 15 13 .......x....... ...o...x....*.. .......x....... .......x....... .......x....... ............... xxxxx.....xxxxx ............... .......x....... .......x....... .......x....... ..*....x....*.. .......x....... 10 10 .......... ..o....... .......... .......... .......... .....xxxxx .....x.... .....x.*.. .....x.... .....x.... 0 0
Sample Output
8 49 -1
分析:BFS得到邻接矩阵,这样就是一个固定起点的TSP问题,再用递归DFS(也叫回溯法)+剪枝,就可以得到答案。
问题:输入数据是连续的,直到0 0终止。倒腾了好久都是WA,居然是这个原因。。。。
1 #include <stdio.h> 2 #include <stdlib.h> 3 4 #define MAX_MAX 65535 5 #define MAX_ROOM 25 6 #define MAX_DIRT 15 7 #define Q_LEN 10000 8 9 typedef struct 10 { 11 int x; 12 int y; 13 int step; 14 }T_Node; 15 16 const int deltax[4] = {-1, 0, 1, 0}; 17 const int deltay[4] = {0, 1, 0, -1}; 18 19 T_Node gatDirt[MAX_DIRT]; 20 T_Node queue[Q_LEN]; 21 int gwLen; 22 int gwWide; 23 int gwDirtNum = 1; 24 char gawMap[MAX_ROOM][MAX_ROOM]; 25 int gawDist[MAX_DIRT][MAX_DIRT]; 26 27 int BFS(T_Node *ptStart, T_Node *ptEnd) 28 { 29 int head = 0; 30 int tail = 1; 31 int direction = 0; 32 char Map[MAX_ROOM][MAX_ROOM]; 33 queue[head] = *ptStart; 34 35 int i,j; 36 for(j=0; j<gwLen; j++) 37 { 38 for(i=0; i<gwWide; i++) 39 { 40 Map[j][i] = gawMap[j][i]; 41 } 42 } 43 44 Map[ptStart->y][ptStart->x] = 'x'; 45 while(head != tail) 46 { 47 for(direction=0; direction<4; direction++) 48 { 49 if(queue[head].x + deltax[direction] < 0 50 || queue[head].x + deltax[direction] >= gwWide 51 || queue[head].y + deltay[direction] < 0 52 || queue[head].y + deltay[direction] >= gwLen) 53 continue; 54 queue[tail].x = queue[head].x + deltax[direction]; 55 queue[tail].y = queue[head].y + deltay[direction]; 56 if(queue[tail].x == ptEnd->x && queue[tail].y == ptEnd->y) 57 { 58 return queue[head].step + 1; 59 } 60 if(Map[queue[tail].y][queue[tail].x] != 'x') 61 { 62 queue[tail].step = queue[head].step + 1; 63 Map[queue[tail].y][queue[tail].x] = 'x'; 64 tail++; 65 } 66 } 67 head++; 68 } 69 return -1; 70 } 71 72 int gawIsCleaned[MAX_DIRT]; 73 int gwBest = MAX_MAX; 74 75 void DFS(int sum, int position, int deep) 76 { 77 int k = 0; 78 int ThisSum = sum; 79 deep++; 80 if(deep == gwDirtNum) 81 if(sum < gwBest) 82 { 83 gwBest = sum; 84 return; 85 } 86 for(k=0; k<gwDirtNum; k++) 87 { 88 if(gawDist[position][k] ==0 || gawIsCleaned[k] ==1) 89 { 90 continue; 91 } 92 sum += gawDist[position][k]; 93 if(sum > gwBest) 94 break; 95 gawIsCleaned[position] = 1; 96 DFS(sum, k, deep); 97 sum = ThisSum; 98 gawIsCleaned[position] = 0; 99 } 100 return; 101 } 102 103 int main(void) 104 { 105 int i,j; 106 while(scanf("%d %d", &gwWide, &gwLen)) 107 { 108 getchar(); 109 if(gwWide == 0 || gwLen == 0) 110 { 111 return 0; 112 } 113 gwDirtNum = 1; 114 for(j=0; j<gwLen; j++) 115 { 116 for(i=0; i<gwWide; i++) 117 { 118 scanf("%c", &gawMap[j][i]); 119 if(gawMap[j][i] == '*') 120 { 121 gatDirt[gwDirtNum].x = i; 122 gatDirt[gwDirtNum].y = j; 123 gwDirtNum++; 124 } 125 if(gawMap[j][i] == 'o') 126 { 127 gatDirt[0].x = i; 128 gatDirt[0].y = j; 129 } 130 } 131 getchar(); 132 } 133 for(j=0; j<gwDirtNum; j++) 134 { 135 for(i=j+1; i<gwDirtNum; i++) 136 { 137 gawDist[j][i] = BFS(&gatDirt[i], &gatDirt[j]); 138 if(gawDist[j][i] == -1) 139 { 140 gwBest = 0; 141 break; 142 } 143 if(j != 0) gawDist[i][j] = gawDist[j][i]; 144 } 145 } 146 147 if(gwBest == 0) 148 { 149 gwBest = MAX_MAX; 150 printf("-1\n"); 151 } 152 else 153 { 154 gwBest = MAX_MAX; 155 DFS(0, 0, 0); 156 printf("%d\n", gwBest); 157 } 158 } 159 return 0; 160 }